﻿#define _CRT_SECURE_NO_WARNINGS 1

#include<iostream>
#include<string>
using namespace std;

//int main()
//{
//	int* p = new int(0);
//	int b = 1;
//	const int c = b;
//	*p = 10;
//	string s("111111");
//	s[0] = 'x';
//	double x = 1.1, y = 2.2;
//	// 左值引用给左值取别名 
//	int& r1 = b;
//	int*& r2 = p;
//	int& r3 = *p;
//	string& r4 = s;
//	char& r5 = s[0];
//
//	// 右值引用给右值取别名
//	int&& rr1 = 10;
//	double&& rr2 = x + y;
//	double&& rr3 = fmin(x, y);
//	string&& rr4 = string("11111");
//
//	// const左值引用引用右值
//	const int& rr1 = 10;
//	const double& rr2 = x + y;
//	const double& rr3 = fmin(x, y);
//	const string& rr4 = string("11111");
//
//	// 右值引用引用move(左值)
//	int&& r1 = move(b);
//	int*&& r2 = move(p);
//	int&& r3 = move(*p);
//	string&& r4 = move(s);
//	char&& r5 = move(s[0]);
//
//	
//	return 0;
//}

//int main()
//{
//	int&& rr1 = 10;
//	// rr1的类型是右值引用
//	int& rrr1 = rr1;
//	// 但是rr1的属性是左值，因为右值是字面量常量、表达式求值产生的临时对象和匿名对象
//	// 所以rr1的属性是左值
//	cout << &rr1 << endl;
//	return 0;
//}

//int main()
//{
//	int r = 10;
//	int& r1 = r;
//	int&& rr1 = 10;
//
//	return 0;
//}

//int main()
//{
//	string s1 = "Test";
//	string& rs1 = s1;
//	// std::string&& r1 = s1; // 错误：不能绑定到右值 
//	const std::string& r2 = s1 + s1; // OK：const 的左值引用延⻓生存期 
//	// r2 += "Test"; // 错误：不能通过到 const 的引用修改 
//	std::string&& r3 = s1 + s1; // OK：右值引用延⻓生存期 
//	r3 += "Test"; // OK：能通过到非 const 的引用修改，r3的属性是左值，可以修改 
//	std::cout << r3 << '\n';
//	return 0;
//}
//template<class T>
//void func(const T& t)
//{
//	cout << "func(const T & t)" << endl;
//}
//
//int main()
//{
//	int i = 10;
//	const int j = 20;
//	func(i);// 左值
//	func(j);// const左值引用的右值
//	func(30);// 右值
//	return 0;
//}

//void f(int& x)
//{
//	std::cout << "左值引用重载 f(" << x << ")\n";
//}
//void f(const int& x)
//{
//	std::cout << "const 的左值引用重载 f(" << x << ")\n";
//}
//void f(int&& x)
//{
//	std::cout << "右值引用重载 f(" << x << ")\n";
//}
//int main()
//{
//	int i = 1;
//	const int ci = 2;
//	f(i); // 左值，调用 f(int&) 
//	f(ci); // const修饰的左值，调用 f(const int&) 
//	f(3); // 右值，调用 f(int&&)，如果没有 f(int&&) 重载则会调用 f(const int&) 
//	f(std::move(i)); // 强转为右值，调用 f(int&&) 
//	// 右值引用变量在用于表达式时是左值 
//	int&& x = 1;
//	f(x); // x是左值，调用 f(int& x) 
//	f(std::move(x)); // 强转为右值，调用 f(int&& x) 
//	return 0;
//}

class Solution {
public:
    int lengthOfLongestSubstring(string s) {
        int hash[128] = { 0 };
        int left = 0, right = 0, len = INT_MIN;
        while (left <= right && right < s.size())
        {
            // 入窗口
            hash[s[right]]++;// 映射 
            // 判断
            if (hash[s[right]] > 1)
            {
                while (left < right && s[left] != s[right]) // 找相等
                {
                    hash[s[left]]--;
                    ++left;
                }
                hash[s[left]]--;
                ++left;
            }
            len = max(len, right - left + 1);
            ++right;
        }
        return len == INT_MIN ? 0 : len;
    }
};
int main()
{
    Solution s;
    cout<<s.lengthOfLongestSubstring("kgquqbcycmqtfkbem");
    return 0;
}